/*
 *  CELocale.h
 *  LID Library
 *
 *  Created by Alexander Trutchenko on 05/11/12.
 *  Copyright 2011 League of Independent Developers. All rights reserved.
 *
 */

#ifndef __CE_Locale_h__
#define __CE_Locale_h__


#include <map>
#include <string>
#include <vector>

#include "lid_lib/src/types/LLTypes.h"

namespace cocos2d
{
class CCScene;
class CCBMFontConfiguration;
}

namespace cocosext {

class CELocale;

#define CELOCALE CELocale::sharedLocale() 

        
////////////////////////////////////////////////////////
//
/** CELocale
* Is a class which supports getting localized strings by key from dictionary and localized resources pathes
* We should have the following folder structure
*   <localized root foldef>
*       <rus>
*           dictionary.plist        - localized russian dictionary
*           font1.fnt               - font1.fnt for ENGLIHS AND RUSSIAN UNICODE pages
*           font1.png               - font1.png is a texture for font1.fnt
*           font2.fnt
*           font2.png
*           font3.fnt
*           font3.png
*           texture1.png            - russian localized texture1
*           texture2.png            - russian localized texture2
*
*       <eng>
*           dictionary.plist        - localized english dictionary
*           font1.fnt               - font1.fnt for only english UNICODE page
*           font1.png               - font1.png is a texture for font1.fnt
*           font2.fnt
*           font2.png
*           font3.fnt
*           font3.png
*           texture1.png            - english localized texture1
*           texture2.png            - english localized texture2
*
*       dictionary.plist            - base key list. All dictionaries must have this keys
*/
////////////////////////////////////////////////////////


////////////////////////////////////////////////////////
//
/** CELaguageInfo
*/
////////////////////////////////////////////////////////

typedef std::vector<std::string> CEStrings;
typedef std::map<std::string, std::wstring> CELangDictionary;
typedef std::map<wchar_t, wchar_t> CEWCharToWChar;
struct CELaguageInfo
{
	CELangDictionary _dictionary; 
	CEWCharToWChar _lowerCaseToUpper; 
	CEWCharToWChar _upperToLowerCase;
};

////////////////////////////////////////////////////////
//
/** CELocale
*/
////////////////////////////////////////////////////////

class CEFNTConfigInfo;
typedef std::map<std::string, unsigned int> CEResourceRefs;

class CELocale
{
	typedef std::map<std::string, CELaguageInfo> CELaguages;
	typedef std::map<cocos2d::CCScene*, CEFNTConfigInfo*> CESceneFNTConfigs;

private:
	std::string _localizationSourcesRootFolderRelative;
	std::string _dictionaryFileName;
	std::string _localizationSourcesRootFolderFull;
	std::string _checkFileName;
    
	CEStrings _suportedLanguages;

	CELaguages _loadedLanguages;
	
	std::string _currentLanguage;
	CELaguageInfo* _currentLanguageInfo;
	bool _saveCurrentLanguage;


	CEResourceRefs _atlasRefs;
	CESceneFNTConfigs _sceneFntConfigs;
	CEFNTConfigInfo* _currentConfig;
	cocos2d::CCScene* _currentScene;


private:
	static CELocale* _instance;

private:
    CELocale(const char* localizationSourcesRootFolder, const char* dictionaryFileName, const char* checkFileName, bool saveCurrentLanguage);
	~CELocale();

	bool init();

public:
	static void createAndInit(const char* localizationSourcesRootFolder, const char* dictionaryFileName, const char* checkFileName = "", bool saveCurrentLanguage = false);
	static CELocale* sharedLocale() { return _instance; }
    static void pvt_remove();

	
public:
//Main interface

	// Work with current language
	const std::string& currentLanguage() const { return _currentLanguage; }
	void setCurrentLanguage(const std::string& newLanguage);

	// Work with dictionary and path
	const wchar_t* strForKey(const std::string& key, const std::string& language = "") const;
    const char* languageFilePath(const std::string& relativeToLanguageFolderPath, const std::string& language = "") const;

	// Work with alphabets 
	wchar_t locToWLower(wchar_t ch, const std::string& language = "") const;
	wchar_t locToWUpper(wchar_t ch, const std::string& language = "") const;

	// Work with all languages
	const CEStrings& suportedLanguages() const { return _suportedLanguages; } //"rus", "eng" etc - iso 639-3
	CEStrings loadedLanguages() const;
	bool loadLanguage(const std::string& language);
	void unloadLanguage(const std::string& language);

	// Resource managment
	void addLocalizedFNTConfig(const std::string& fntFile);
	void addLocalizedSpriteFramesWithFile(const std::string& atlasName);
	void addLocalizedTextureWithFile(const std::string& fileName);

    void onAddScene(cocos2d::CCScene* scene);
	void onReplaceSceneWithTheSameResources(cocos2d::CCScene* oldScene, cocos2d::CCScene* newScene);
    void onRemoveScene(cocos2d::CCScene* scene);
	void setCurrentScene(cocos2d::CCScene* scene);

private:
	const CELaguageInfo* languageInfo(const std::string& language) const;

	void loadCurrentLanguageName();
	void saveCurrentLanguageName() const;
};

}// 

#endif //__CE_Locale_h__
 